package com.baseweb.webadmin.controller.admin;

import com.baseweb.webadmin.alipay.util.AlipayNotify;
import com.baseweb.webadmin.alipay.util.AlipayParams;
import com.baseweb.webadmin.controller.BaseController;
import com.baseweb.webadmin.core.constants.*;
import com.baseweb.webadmin.core.model.bvo.ByUserWithdrawBvo;
import com.baseweb.webadmin.core.model.pojo.*;
import com.baseweb.webadmin.core.util.*;
import com.baseweb.webadmin.service.AccountService;
import com.baseweb.webadmin.service.RoleService;
import com.baseweb.webadmin.service.UserService;
import org.apache.commons.lang.StringUtils;
import org.apache.shiro.authc.Account;
import org.joda.time.DateTime;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

@Controller
@RequestMapping(value = "/account")
public class AccountController extends BaseController {

    private static final Logger LOG = LoggerFactory.getLogger(AccountController.class);

    @Autowired
    private RoleService roleService;

    @Autowired
    private AccountService accountService;

    @Autowired
    private UserService userService;

    private String PREFIX = "/account/";

    @RequestMapping(value = "/coinsLog")
    public String coinsLog() {
        return PREFIX + "coinsLog";
    }

    @RequestMapping(value = "/getCoinsLogsList")
    public void getCoinsLogsList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                                     @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                                     Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

        User user = getCurrentUser();
        List<ByCoinsLog> list = accountService.selectCoinsLogListByPage(user.getId(), (page-1)*pageSize, pageSize);
        int total = accountService.selectCoinsLogListCount(user.getId());
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }


    @RequestMapping(value = "/moneyLog")
    public String moneyLog() {
        return PREFIX + "moneyLog";
    }

    @RequestMapping(value = "/getMoneyLogsList")
    public void getMoneyLogsList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                                     @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                                     Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }
        User user = getCurrentUser();
        List<ByMoneyLog> list = accountService.selectMoneyLogListByPage(user.getId(), (page-1)*pageSize, pageSize);
        int total = accountService.selectMoneyLogListCount(user.getId());
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }

    @RequestMapping(value = "/voucherManage")
    public String voucherManage() {
        return PREFIX + "voucherManage";
    }

    @RequestMapping(value = "/getVoucherList")
    public void getVoucherList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                               @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                               @RequestParam(value = "user_id", defaultValue = "") Integer userId,
                               Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

        List<ByUserVoucher> list = accountService.selectVoucherListByPage(userId, (page-1)*pageSize, pageSize);
        int total = accountService.selectVoucherListCount(userId);
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }

    @RequestMapping(value = "/myVoucher")
    public String myVoucher() {
        return PREFIX + "myVoucher";
    }

    @RequestMapping(value = "/getMyVoucherList")
    public void getMyVoucherList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                                 @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                                 Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

        User user = getCurrentUser();
        List<ByUserVoucher> list = accountService.selectVoucherListByPage(user.getId(), (page-1)*pageSize, pageSize);
        int total = accountService.selectVoucherListCount(user.getId());
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }






    //提现账户管理
    @RequestMapping(value = "/addWithdrawAccountView")
    public String addWithdrawAccountView(@RequestParam(value = "id",required = false) Integer id,
                                 Model model) {

        boolean is_writable = true;

        User user = getCurrentUser();
        List<Role> userRoles = roleService.selectRoleListByUser(user.getId().toString());

        for(Role current : userRoles) {
            if ((current.getId().intValue() == RoleType.NORMAL_BIZ.getCode())
                    || (current.getId().intValue() == RoleType.NORMAL_USER.getCode()))
            {
                is_writable = false;
                break;
            }
        }

        if (is_writable){
            model.addAttribute("is_writable", is_writable);
        }
        model.addAttribute("bankTypeList", BankType.getAllData());
        return PREFIX + "addWithdrawAccountView";
    }

    @RequestMapping(value = "/editWithdrawAccountView")
    public String editWithdrawAccountView(@RequestParam(value = "id",required = false) Integer id,
                                  Model model) {

        if (id != null && id > 0){
            model.addAttribute("withdrawAccount", accountService.findWithdrawAccount(id));
        }

        boolean is_writable = true;

        User user = getCurrentUser();
        List<Role> userRoles = roleService.selectRoleListByUser(user.getId().toString());

        for(Role current : userRoles) {
            if ((current.getId().intValue() == RoleType.NORMAL_BIZ.getCode())
                    || (current.getId().intValue() == RoleType.NORMAL_USER.getCode()))
            {
                is_writable = false;
                break;
            }
        }

        if (is_writable){
            model.addAttribute("is_writable", is_writable);
        }
        model.addAttribute("bankTypeList", BankType.getAllData());
        return PREFIX + "editWithdrawAccountView";
    }

    @RequestMapping(value = "/submitWithdrawAccountView")
    public String submitWithdrawAccountView(@RequestParam(value = "id",required = false) Integer id,
                               @RequestParam(value = "user_id",required = false) Integer user_id,
                               @RequestParam(value = "name",required = false) String name,
                               @RequestParam(value = "bank_type",required = false) Integer bank_type,
                               @RequestParam(value = "open_from",required = false) String open_from,
                               @RequestParam(value = "account_num",required = false) String account_num,
                               @RequestParam(value = "descn",required = false) String descn,
                               @RequestParam(value = "status",required = false) Integer status,
                               Model model) {
        try{
            ByUserWithdrawAccount byUserWithdrawAccount = null;
            if (id != null && id > 0){
                byUserWithdrawAccount = accountService.findWithdrawAccount(id);
            }else{
                byUserWithdrawAccount = new ByUserWithdrawAccount();
            }

            User user = getCurrentUser();
            byUserWithdrawAccount.setUserId(user.getId());
            byUserWithdrawAccount.setBankType(bank_type);
            byUserWithdrawAccount.setName(name);
            byUserWithdrawAccount.setOpenFrom(open_from);
            byUserWithdrawAccount.setAccountNum(account_num);
            byUserWithdrawAccount.setDescn(descn);
            byUserWithdrawAccount.setStatus(status);
            byUserWithdrawAccount.setCreateTime(new DateTime());
            byUserWithdrawAccount.setUpdateTime(new DateTime());

            accountService.insertWithdrawAccount(byUserWithdrawAccount);
            model.addAttribute("result", true);
        }catch (Exception ex){
            ex.printStackTrace();
            model.addAttribute("result", false);
        }
        return PREFIX + "withdrawAccountManage";
    }

    @RequestMapping(value = "/withdrawAccountManage")
    public String withdrawAccountManage() {
        return PREFIX + "withdrawAccountManage";
    }

    @RequestMapping(value = "/getWithdrawAccountList")
    public void getWithdrawAccountList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                                 @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                                 Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

        User user = getCurrentUser();
        List<ByUserWithdrawAccount> list = accountService.selectWithdrawAccountListByPage(user.getId(), (page-1)*pageSize, pageSize);
        int total = accountService.selectWithdrawAccountListCount(user.getId());
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }

    //我要提现,提现管理
    @RequestMapping(value = "/addWithdrawView")
    public String addWithdrawView(@RequestParam(value = "id",required = false) Integer id,
                                 Model model) {

        boolean is_writable = true;

        User user = getCurrentUser();
        List<Role> userRoles = roleService.selectRoleListByUser(user.getId().toString());

        for(Role current : userRoles) {
            if ((current.getId().intValue() == RoleType.NORMAL_BIZ.getCode())
                    || (current.getId().intValue() == RoleType.NORMAL_USER.getCode()))
            {
                is_writable = false;
                break;
            }
        }

        if (is_writable){
            model.addAttribute("is_writable", is_writable);
        }

        model.addAttribute("accountList", accountService.selectWithdrawAccountListByPage(user.getId(), 0, Integer.MAX_VALUE));
        return PREFIX + "addWithdrawView";
    }

    @RequestMapping(value = "/editWithdrawView")
    public String editWithdrawView(@RequestParam(value = "id",required = false) Integer id,
                                  Model model) {

        if (id != null && id > 0){
            model.addAttribute("withdraw", accountService.findWithdraw(id));
        }

        boolean is_writable = true;

        User user = getCurrentUser();
        List<Role> userRoles = roleService.selectRoleListByUser(user.getId().toString());

        for(Role current : userRoles) {
            if ((current.getId().intValue() == RoleType.NORMAL_BIZ.getCode())
                    || (current.getId().intValue() == RoleType.NORMAL_USER.getCode()))
            {
                is_writable = false;
                break;
            }
        }

        if (is_writable){
            model.addAttribute("is_writable", is_writable);
        }

        model.addAttribute("accountList", accountService.selectWithdrawAccountListByPage(user.getId(), 0, Integer.MAX_VALUE));
        return PREFIX + "editWithdrawView";
    }

    @RequestMapping(value = "/submitWithdraw")
    public String submitWithdraw(@RequestParam(value = "id",required = false) Integer id,
                               @RequestParam(value = "account_id",required = false) Integer account_id,
                               @RequestParam(value = "amount",required = false) String amount,
                               @RequestParam(value = "descn",required = false) String descn,
                               @RequestParam(value = "status",defaultValue = "-1") Integer status,
                               Model model) {
        try{
            ByUserWithdraw byUserWithdraw = null;
            if (id != null && id > 0){
                byUserWithdraw = accountService.findWithdraw(id);
            }else{
                byUserWithdraw = new ByUserWithdraw();
            }

            User user = getCurrentUser();
            byUserWithdraw.setUserId(user.getId());
            byUserWithdraw.setAccountId(account_id);
            byUserWithdraw.setDescn(descn);
            byUserWithdraw.setAmount(ObjectFormatter.str2BigDecimal(amount));
            byUserWithdraw.setStatus(status);
            byUserWithdraw.setCreateTime(new DateTime());
            byUserWithdraw.setUpdateTime(new DateTime());

            accountService.insertWithdraw(byUserWithdraw);
            model.addAttribute("result", true);
        }catch (Exception ex){
            ex.printStackTrace();
            model.addAttribute("result", false);
        }
        return PREFIX + "myWithdraw";
    }

    @RequestMapping(value = "/myWithdraw")
    public String myWithdraw() {
        return PREFIX + "myWithdraw";
    }

    @RequestMapping(value = "/getMyWithdrawList")
    public void getMyWithdrawList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                               @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                               Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

        User user = getCurrentUser();
        List<ByUserWithdrawBvo> list = new ArrayList<ByUserWithdrawBvo>();
        List<ByUserWithdraw> byUserWithdraws = accountService.selectWithdrawListByPage(user.getId(), (page-1)*pageSize, pageSize);

        for (ByUserWithdraw current : byUserWithdraws){
            ByUserWithdrawBvo bvo = ByUserWithdrawBvo.copyFrom(current, userService.selectUserById(current.getUserId()),
                    accountService.findWithdrawAccount(current.getAccountId()));

            list.add(bvo);
        }
        int total = accountService.selectWithdrawListCount(user.getId());

        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }

    @RequestMapping(value = "/withdrawManage")
    public String withdrawManage() {
        return PREFIX + "withdrawManage";
    }

    @RequestMapping(value = "/getWithdrawList")
    public void getWithdrawList(@RequestParam(value = "page", defaultValue = "1") Integer page,
                                @RequestParam(value = "pageSize", defaultValue = "20") Integer pageSize,
                                @RequestParam(value = "user_id", required = false) Integer user_id,
                                 Model model) {
        if (pageSize == null || pageSize == 0) {
            pageSize = 20;
        }

//        User user = getCurrentUser();
        List<ByUserWithdrawBvo> list = new ArrayList<ByUserWithdrawBvo>();
        List<ByUserWithdraw> byUserWithdraws = accountService.selectWithdrawListByPage(null, (page-1)*pageSize, pageSize);

        for (ByUserWithdraw current : byUserWithdraws){
            ByUserWithdrawBvo bvo = ByUserWithdrawBvo.copyFrom(current, userService.selectUserById(current.getUserId()),
                    accountService.findWithdrawAccount(current.getAccountId()));

            list.add(bvo);
        }

        int total = accountService.selectWithdrawListCount(null);
        model.addAttribute("list", list);
        model.addAttribute("total", total);
        model.addAttribute("pageSize", pageSize);
    }

    @RequestMapping(value = "/submitWithdrawStatus")
    public String submitWithdrawStatus(@RequestParam(value = "id",required = false) Integer id,
                                 Model model) {
        try{
            ByUserWithdraw byUserWithdraw = null;
            if (id != null && id > 0){
                byUserWithdraw = accountService.findWithdraw(id);
            }else{
                byUserWithdraw = new ByUserWithdraw();
            }

            byUserWithdraw.setStatus(WithdrawStatus.SUBMIT.getCode());
            byUserWithdraw.setUpdateTime(new DateTime());

            accountService.insertWithdraw(byUserWithdraw);
            model.addAttribute("result", true);
        }catch (Exception ex){
            ex.printStackTrace();
            model.addAttribute("result", false);
        }

        return PREFIX + "myWithdraw";

    }

    @RequestMapping(value = "/changeWithdrawStatus")
    public String submitWithdraw(@RequestParam(value = "id",required = true) Integer id,
                                 @RequestParam(value = "status",required = true) Integer status,
                                 Model model) {
        try{
            ByUserWithdraw byUserWithdraw = null;
            if (id != null && id > 0){
                byUserWithdraw = accountService.findWithdraw(id);
            }else{
                byUserWithdraw = new ByUserWithdraw();
            }

            if (status == WithdrawStatus.VERIFIED.getCode()) {
                User userWd = userService.selectUserById(byUserWithdraw.getUserId());

                if (userWd.getMoney().compareTo(byUserWithdraw.getAmount()) == -1){
                    model.addAttribute("result", "用户"+userWd.getCnName()+"账户余额不足,无法提现!");
                    return PREFIX + "withdrawManage";
                }

                writeMoneyLog(userWd, MoneyType.WITHDRAW_MONEY.getCode(), BigDecimal.ZERO.subtract(byUserWithdraw.getAmount()));
            }
            byUserWithdraw.setStatus(status);
            byUserWithdraw.setUpdateTime(new DateTime());

            accountService.insertWithdraw(byUserWithdraw);

            model.addAttribute("result", true);
        }catch (Exception ex){
            ex.printStackTrace();
            model.addAttribute("result", false);
        }

        return PREFIX + "withdrawManage";
    }
}
